<?php
/**
 * 商品类别的管理 （只有三级分类） 目前只要一级了
 * Author: lyun
 * Date: 2018/3/27
 * Created by Panxsoft.
 */


namespace App\Http\Controllers\Admin\Panx\Product;

use App\Http\Controllers\ApiController;
use App\Http\Requests\Admin\Panx\Product\CategoryStoreRequest;
use App\Http\Requests\Admin\Panx\Product\CategoryUpdateRequest;
use App\Models\Admin\PanxAdmin;
use App\Models\Customer\Language;
use App\Models\Panx\Category;
use App\Models\Panx\CategoryDescription;
use App\Services\Utils\Transaction;
use Illuminate\Database\Eloquent\Collection;
use Illuminate\Http\Request;

class ProductCategoryController extends ApiController
{
    const ROUTES = [
        'index'   => 'api.admin.panx.category.index',
        'store'   => 'api.admin.panx.category.store',
        'update'  => 'api.admin.panx.category.update',
        'destroy' => 'api.admin.panx.category.delete',
    ];

    /**
     * Display a listing of the resource.
     * @test
     *
     * @param Request $request
     * @return \Illuminate\Http\Response
     * @throws \Exception
     */
    public function index(Request $request)
    {
        $this->checkIsTrue(PanxAdmin::checkIsSuperMan(), trans('admin.is_super_man'));

        $categories = Category::where('parent_id', Category::TOP_CATEGORY)
//            ->with('allChildrenCategories')
            ->with('categoryDescriptions')
            ->latest('priority')
            ->paginate($request->per_page?:15);

        return $this->response(compact('categories'));
    }

    /**
     *
     * Show the form for creating a new resource.
     *
     * @return \Illuminate\Http\Response
     */
    public function create()
    {
        /** @var Collection $goods_categories */
//        $goods_categories = Category::where('parent_id', Category::TOP_CATEGORY)
//            ->with('getChildCategory')
//            ->get();
//
//        $goods_categories = $goods_categories->prepend(collect(['id'=>0, 'name'=>'顶级分类', 'level'=>0]));

        $languages = Language::all();

        return $this->response(compact('languages'));
    }

    /**
     * Store a newly created resource in storage.
     * @test
     *
     * @param  CategoryStoreRequest  $request
     * @return \Illuminate\Http\Response
     * @throws \Exception
     */
    public function store(CategoryStoreRequest $request)
    {
        // 超管才能添加的
        $this->checkIsTrue(PanxAdmin::checkIsSuperMan(), trans('admin.is_super_man'));

        $goods_category = $this->assembleGoodsCategory($request);
        $category_names = $request->category_names;

        $stored = Transaction::handle(function() use($goods_category, $category_names){
            $stored = Category::create($goods_category);
            $this->storeCategoryDescription($category_names, $stored->id);

            return $stored;
        });

        return $this->response(compact('stored'));
    }

    /**
     * Update the specified resource in storage.
     * @test
     *
     * @param  CategoryUpdateRequest  $request
     * @param  int  $id
     * @return \Illuminate\Http\Response
     * @throws \Exception
     */
    public function update(CategoryUpdateRequest $request, $id)
    {
        // 超管才能更新
        $this->checkIsTrue(PanxAdmin::checkIsSuperMan(), trans('admin.is_super_man'));

        /** @var Category $category */
        $category = Category::find($id);
            $this->checkCanUpdate($category);

        $category_data = $this->assembleGoodsCategory($request);

        // 检测是否将自己的下级改成上级
//        $is_bool = $category->checkIsMoveToChild($request->parent_id);
//            $this->checkIsTrue(!$is_bool, '不能将子类改成上级');

        // 检测是否将第三级改成上级 （不用了，create方法返回的只是一级和二级id）
//        $is_bool = $category->checkIsMoveToThreeChild($request->parent_id);
//            $this->checkIsTrue($is_bool, '上级不能是第三级');

        // 不能更改parent_id
        unset($category_data['parent_id']);
        $category_names = $request->category_names;

        $updated = Transaction::handle(function() use($category, $category_data, $category_names){
            $updated = $category->update($category_data);
            CategoryDescription::where('category_id', $category->id)->delete();
            $this->storeCategoryDescription($category_names, $category->id);

            return $updated;
        });

        return $this->response(compact('updated'));
    }

    /**
     * Remove the specified resource from storage.
     * @test
     *
     * @param  int $id
     * @return \Illuminate\Http\Response
     * @throws \Exception
     */
    public function destroy($id)
    {
        // 超管才能删除的
        $this->checkIsTrue(PanxAdmin::checkIsSuperMan(), trans('admin.is_super_man'));

        /** @var Category $category */
        $category = Category::find($id);
            $this->checkCanDestroy($category);

        $deleted = Transaction::handle(function() use($category){
            $category->categoryDescriptions()->delete();
            $deleted = $category->delete();

            return $deleted;
        });

        return $this->response(compact('deleted'));
    }

    /**
     * @param CategoryStoreRequest|CategoryUpdateRequest|Request $request
     * @return array
     * @throws \Exception
     */
    private function assembleGoodsCategory(Request $request): array
    {
        $category_names = $request->category_names;
        $language_ids = $request->language_ids;

        foreach($category_names as $item)
        {
            if ((int)$item['language_id'] === (int)$language_ids[Language::ZH_CN]) {
                $name = $item['name'];
            } else if ((int)$item['language_id'] === (int)$language_ids[Language::EN]) {
                $const = $item['name'];
            } else {
               continue;
            }
        }

        $data = [
            'name'        => $name ?? '',
            'const'       => $const ?? '',
            'parent_id'   => $request->parent_id,
            'priority'    => $request->priority,
            'has_asset'   => $request->has_asset,
        ];

        if ($request->has('icon')) {
            $data['icon'] = $request->icon;
        }

        return $data;
    }

    /**
     * @param $category
     * @throws \Exception
     */
    private function checkCanUpdate(?Category $category): void
    {
        $this->checkItemExist($category, trans('admin.category'));

//        $this->checkUnless($category->isInitialCategory(), '不能修改Panx设置的顶级分类');
    }

    /**
     * @param $category
     * @throws \Exception
     */
    private function checkCanDestroy(?Category $category): void
    {
        $this->checkItemExist($category, trans('admin.category'));

//        $this->checkUnless($category->isInitialCategory(), 'Panx预设的顶级分类，不能删除！');

        // 是否有客户开通此类别功能
        $this->checkUnless($category->hasCustomerOperateCategory(), trans('admin.has_customer_use_category'));

        $this->checkUnless($category->hasChildrenAndHasGoods(), trans('admin.has_product_use_category'));
    }

    /**
     * @param array $category_names
     * @param $category_id
     * @return mixed
     */
    private function storeCategoryDescription(array $category_names, $category_id)
    {
        $data = array_map(function($item) use($category_id){
            return array_merge(['category_id' => $category_id], $item);
        }, $category_names);

        $stored = CategoryDescription::insert($data);

        return $stored;
    }
}
